package com.gujh.security.config;

import com.gujh.security.authentication.SecurityAuthenticationHandler;
import com.gujh.security.authentication.json.JsonLoginConfigurer;
import lombok.AllArgsConstructor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer;
import org.springframework.security.web.SecurityFilterChain;

@Configuration
@AllArgsConstructor
public class SpringSecurityConfig {

    private SecurityAuthenticationHandler securityAuthenticationHandler;

    private JsonLoginConfigurer<HttpSecurity> jsonLoginConfigurer;

    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        http
                .securityMatcher("/**")
                .authorizeHttpRequests(request -> request
                        .requestMatchers("/login**", "/logout").permitAll()
                        .requestMatchers("*.css", "*.js").permitAll()
                        .anyRequest().authenticated())
                .exceptionHandling(exception -> exception
                        .authenticationEntryPoint(securityAuthenticationHandler)
                        .accessDeniedHandler(securityAuthenticationHandler))
                .formLogin(form -> form
                        .loginProcessingUrl("/login/form")
                        .successHandler(securityAuthenticationHandler)
                        .failureHandler(securityAuthenticationHandler))
                .logout(logout -> logout
                        .logoutUrl("/logout")
                        .logoutSuccessHandler(securityAuthenticationHandler)
                        .clearAuthentication(true))
                .csrf(AbstractHttpConfigurer::disable);
        http
                .apply(jsonLoginConfigurer)
                .loginProcessingUrl("/login/json")
                .usernameParameter("username")
                .passwordParameter("password")
                .setSuccessHandler(securityAuthenticationHandler)
                .setFailureHandler(securityAuthenticationHandler);

        return http.build();
    }

}
